#include "Block Grid.h"
#include <fstream>
#include <sstream>
#include <iostream>
using namespace std;

#define Words		4
void BlockGrid::Initialize(XY Pos,char * MapName) {

	int Characters = 0;
	int i;
	for(i = 0;MapName[i];i++) {
		Characters++;
	}
	ChunkPos = Pos;
	Active = false;
	char ** Name = new char*[Words];
	for(i = 0;i < Words;i++)
		Name[i] = new char[++Characters];
	for(i = 0;MapName[i];i++) {
		Name[0][i] = MapName[i];
	}
	Name[0][i] = '\\';
	Name[4] = ".txt";
	_itoa_s(Pos.X , Name[1] , Characters , 10);
	_itoa_s(Pos.Y , Name[2] , Characters , 10);
	int size = 0;
	for(int i = 0;i < Words;i++)
		size += strlen(Name[i]);
	int FileItt = 0;
	FileName = new char[size+1];
	for(i = 0;i < Words;i++) {
		for(int j = 0;Name[i][j] && j < Characters;j++) {
			FileName[FileItt++] = Name[i][j];
		}
	}
	FileName[FileItt] = '\0';
	Boundaries.MinX = Pos.X;
	Boundaries.MinY = Pos.Y;
	Boundaries.MaxX = Pos.X + GRID_SIZE;
	Boundaries.MaxY = Pos.Y + GRID_SIZE;
	FillGrid();
	SaveToFile();
}

void BlockGrid::Store()
{
	SaveToFile();
	ClearGrid();
}

void BlockGrid::FillGrid()
{
	XY CursorPos(0,0);
	char Flag;
	int number = 0;
	int undefined = GRID_SIZE * GRID_SIZE;
	ifstream in;
	in.open(FileName,ios::in);
	
	while(!in.eof() && CursorPos.Y < GRID_SIZE)
	{
		in >> Flag;
		switch(Flag)
		{
		case '!': in >> Flag; MakeBlocks(Flag,GRID_SIZE*GRID_SIZE,&CursorPos);
			number = undefined;
			break;
		case UNKNOWN_TYPE_FLAG:
		case AIR_FLAG:
			in >> number;
			MakeBlocks(AIR_FLAG,number,&CursorPos);
			break;
		case DIRT_FLAG:
			in >> number;
			MakeBlocks(DIRT_FLAG,number,&CursorPos);
			break;
		case WATER_FLAG:
			in >> number;
			MakeBlocks(WATER_FLAG,number,&CursorPos);
			break;
		default:
			MakeBlocks(AIR_FLAG,GRID_SIZE*GRID_SIZE,&CursorPos);
			number = undefined;
			break;
		}
		undefined -= number;
	}
	if(undefined > 0 && CursorPos.Y < GRID_SIZE)
		MakeBlocks(AIR_FLAG,undefined,&CursorPos);
	in.close();
}

void BlockGrid::SaveToFile()
{
	char CurrentFlag = Grid[0][0].GetTypeFlag();
	int number = 0;
	ofstream out;
	out.open(FileName,ios::out);
	for(int y = 0;y < GRID_SIZE;++y)
		for(int x = 0;x < GRID_SIZE;++x)
		{
			if(Grid[y][x].GetTypeFlag() != CurrentFlag)
			{
				out << CurrentFlag << number;
				CurrentFlag = Grid[y][x].GetTypeFlag();
				number = 0;
			}
			number++;
		}
	number >= 2500 ? out << '!' << ' ' << CurrentFlag : out << CurrentFlag << number ;
	out << ' ' << UNKNOWN_TYPE_FLAG;
	out.close();
}

void BlockGrid::MakeBlocks(int Tag,int number,XY * CursorPos)
{
	for(int i = number;i > 0;--i)
	{
		Grid[CursorPos->Y][CursorPos->X] = Block(CursorPos->X+1,CursorPos->Y+1,Tag);
		CursorPos->X++;
		if(CursorPos->X == GRID_SIZE)
		{
			CursorPos->X=0;
			CursorPos->Y++;
			if(CursorPos->Y == GRID_SIZE)
				break;
		}
	}
}

void BlockGrid::ClearGrid()
{
	Active = false;
	for(int y = 0;y < GRID_SIZE;++y)
		delete [] Grid[y];
	delete [] Grid;
}